#include "CampaignModellingForm.h"
#include "ui_CampaignModellingForm.h"



#include "ItemDelegate.h"



#include <ClassFeatureProxyModel.h>
#include <SkillProxyModel.h>
#include <FeatProxyModel.h>
#include <ReferenceProxyModel.h>
#include <SynergyProxyModel.h>
#include <RequirementProxyModel.h>
#include <SpecialProxyModel.h>
#include <ItemRoot.h>



#include <QDebug>



CampaignModellingForm::CampaignModellingForm(QWidget *parent) :
        QWidget(parent),
        AbstractModellingForm(),
        ui(new Ui::CampaignModellingForm)
{
    ui->setupUi(this);

    setModel(new ItemModel(this));

    initialize();
}



CampaignModellingForm::CampaignModellingForm(ItemModel *model, QWidget *parent) :
        QWidget(parent),
        AbstractModellingForm(model),
        ui(new Ui::CampaignModellingForm)
{
    ui->setupUi(this);

    setModel(model);

    initialize();
}



CampaignModellingForm::~CampaignModellingForm()
{
    delete ui;
}



void CampaignModellingForm::setModel(ItemModel *model)
{
    qDebug(Q_FUNC_INFO);

    m_model = model;
    if (!m_model) return;

    m_model->setParent(this);
    ui->treeViewData->setModel(m_model);

    ui->lineEditName->setText(m_model->rootItem()->name());

    // character features
    ClassFeatureProxyModel* classProxy = new ClassFeatureProxyModel(this);
    classProxy->setSourceModel(m_model);
    ui->treeViewClassFeatures->setModel(classProxy);

    // skills
    SkillProxyModel* skillProxy = new SkillProxyModel(this);
    skillProxy->setSourceModel(m_model);
    ui->treeViewSkills->setModel(skillProxy);

    // skill synergies
    SynergyProxyModel* synergyProxy = new SynergyProxyModel(this);
    synergyProxy->setSourceModel(m_model);
    ui->treeViewSynergies->setModel(synergyProxy);

    // feats
    FeatProxyModel* featProxy = new FeatProxyModel(this);
    featProxy->setSourceModel(m_model);
    ui->treeViewFeats->setModel(featProxy);

    // feat requirements
    RequirementProxyModel* reqProxy = new RequirementProxyModel(this);
    reqProxy->setSourceModel(m_model);
    ui->treeViewRequirements->setModel(reqProxy);

    // special abilities
    SpecialProxyModel* specProxy = new SpecialProxyModel(this);
    specProxy->setSourceModel(m_model);
    ui->treeViewSpecials->setModel(specProxy);


    if (!m_model->rootItem()->isDirty()) return;

    on_pushButtonName_clicked();
}



void CampaignModellingForm::onAction(const int &action)
{
    switch (action)
    {
    case AddAction:

    case DeleteAction:

    default:
        return;
    }
}



void CampaignModellingForm::initialize()
{
    // raw data tree
    ui->treeViewData->setItemDelegate(new ItemDelegate(this));

    // skill tree
    ItemDelegate* delegate = new ItemDelegate(this);
    delegate->setEditorFilter(SkillProxyModel::RefField, ".Attribute");
    ui->treeViewSkills->setItemDelegate(delegate);

}



void CampaignModellingForm::on_pushButtonName_clicked()
{
    qDebug(Q_FUNC_INFO);

    ui->lineEditName->setReadOnly(false);

    ui->lineEditName->setFocus();
    ui->lineEditName->selectAll();

}



void CampaignModellingForm::on_treeViewSkills_clicked(QModelIndex index)
{
    qDebug() << Q_FUNC_INFO;
    on_treeViewSkills_activated(index);
}



void CampaignModellingForm::on_treeViewSkills_activated(QModelIndex proxyIndex)
{
    qDebug() << Q_FUNC_INFO;
    if (!proxyIndex.isValid()) return;

    QModelIndex nameProxy = proxyIndex.sibling(proxyIndex.row(), SynergyProxyModel::NameField);
    if (!nameProxy.isValid()) return;

    qDebug("skill proxy check");
    SkillProxyModel* skillModel = dynamic_cast<SkillProxyModel*>(ui->treeViewSkills->model());
    if (!skillModel) return;

    qDebug("source index check");
    QModelIndex sourceIndex = skillModel->mapToSource(nameProxy);
    if (!sourceIndex.isValid()) return;

    qDebug("source category check");
    QModelIndex sourceCategoryIndex = sourceIndex.sibling(sourceIndex.row(), AbstractItem::CategoryData);
    if (!sourceCategoryIndex.isValid())
    {
        qDebug("invalid category index");
        return;
    }

    if (sourceCategoryIndex.data(Qt::EditRole).toInt() != ItemCategory_Item)
    {
        qDebug("Category is not item!");
        return;
    }

    QModelIndex sourceIdIndex = sourceIndex.sibling(sourceIndex.row(), AbstractItem::IdData);


    qDebug("reference proxy check");
    ReferenceProxyModel* synergyModel = dynamic_cast<ReferenceProxyModel*>(ui->treeViewSynergies->model());
    if (!synergyModel) return;

    qDebug() << "setting source target:" << sourceIdIndex.data(Qt::EditRole).toString();
    synergyModel->setSourceTarget(sourceIdIndex);
}



void CampaignModellingForm::on_treeViewFeats_clicked(QModelIndex proxyIndex)
{
    on_treeViewFeats_activated(proxyIndex);
}

void CampaignModellingForm::on_treeViewFeats_activated(QModelIndex proxyIndex)
{
    qDebug() << Q_FUNC_INFO;
    if (!proxyIndex.isValid()) return;

    QModelIndex nameProxy = proxyIndex.sibling(proxyIndex.row(), SynergyProxyModel::NameField);
    if (!nameProxy.isValid()) return;

    qDebug("feat proxy check");
    FeatProxyModel* featModel = dynamic_cast<FeatProxyModel*>(ui->treeViewFeats->model());
    if (!featModel) return;

    qDebug("source index check");
    QModelIndex sourceIndex = featModel->mapToSource(nameProxy);
    if (!sourceIndex.isValid()) return;

    qDebug("source category check");
    QModelIndex sourceCategoryIndex = sourceIndex.sibling(sourceIndex.row(), AbstractItem::CategoryData);
    if (!sourceCategoryIndex.isValid())
    {
        qDebug("invalid category index");
        return;
    }

    if (sourceCategoryIndex.data(Qt::EditRole).toInt() != ItemCategory_Item)
    {
        qDebug("Category is not item!");
        return;
    }

    QModelIndex sourceIdIndex = sourceIndex.sibling(sourceIndex.row(), AbstractItem::IdData);


    qDebug("reference proxy check");
    RequirementProxyModel* refModel = dynamic_cast<RequirementProxyModel*>(ui->treeViewRequirements->model());
    if (!refModel) return;

    qDebug() << "setting source target:" << sourceIdIndex.data(Qt::EditRole).toString();
    refModel->setSourceTarget(sourceIdIndex);
}
